package domain

import (
	"encoding/json"
	"time"

	"github.com/google/uuid"
	"gorm.io/gorm"
)

// DataType 数据类型枚举
type DataType string

const (
	DataTypeString    DataType = "string"
	DataTypeNumber    DataType = "number"
	DataTypeBoolean   DataType = "boolean"
	DataTypeDatetime  DataType = "datetime"
	DataTypeReference DataType = "reference"
	DataTypeArray     DataType = "array"
	DataTypeJSON      DataType = "json"
)

// EntityStatus 实体状态枚举
type EntityStatus string

const (
	EntityStatusActive   EntityStatus = "active"
	EntityStatusInactive EntityStatus = "inactive"
	EntityStatusDeleted  EntityStatus = "deleted"
)

// EntityTemplate 实体模板
type EntityTemplate struct {
	ID          uuid.UUID         `json:"id" gorm:"type:char(36);primaryKey"`
	Name        string            `json:"name" gorm:"type:varchar(100);not null;uniqueIndex"`
	DisplayName string            `json:"display_name" gorm:"type:varchar(200)"`
	Description string            `json:"description" gorm:"type:text"`
	IsActive    bool              `json:"is_active" gorm:"default:true"`
	CreatedAt   time.Time         `json:"created_at"`
	UpdatedAt   time.Time         `json:"updated_at"`
	Attributes  []EntityAttribute `json:"attributes" gorm:"foreignKey:EntityTemplateID;constraint:OnDelete:CASCADE"`
}

// BeforeCreate GORM钩子：创建前生成UUID
func (et *EntityTemplate) BeforeCreate(tx *gorm.DB) error {
	if et.ID == uuid.Nil {
		et.ID = uuid.New()
	}
	return nil
}

// EntityAttribute 属性模板别名（用于兼容性）
type EntityAttribute = AttributeTemplate

// AttributeTemplate 属性模板
type AttributeTemplate struct {
	ID               uuid.UUID        `json:"id" gorm:"type:char(36);primaryKey;not null"`
	EntityTemplateID uuid.UUID        `json:"entity_template_id" gorm:"type:char(36);not null;index"`
	Name             string           `json:"name" gorm:"type:varchar(100);not null"`
	DisplayName      string           `json:"display_name" gorm:"type:varchar(200)"`
	DataType         DataType         `json:"data_type" gorm:"type:varchar(20);not null"`
	Required         bool             `json:"required" gorm:"default:false"`
	DefaultValue     *string          `json:"default_value" gorm:"type:text"`
	ValidationRules  *json.RawMessage `json:"validation_rules" gorm:"type:json"`
	SortOrder        int              `json:"sort_order" gorm:"default:0"`
	CreatedAt        time.Time        `json:"created_at"`
	UpdatedAt        time.Time        `json:"updated_at"`

	// 外键关联
	EntityTemplate *EntityTemplate `json:"entity_template,omitempty" gorm:"foreignKey:EntityTemplateID"`
}

// BeforeCreate GORM钩子：创建前生成UUID
func (at *AttributeTemplate) BeforeCreate(tx *gorm.DB) error {
	if at.ID == uuid.Nil {
		at.ID = uuid.New()
	}
	return nil
}

// Entity 实体
type Entity struct {
	ID         uuid.UUID    `json:"id" gorm:"type:char(36);primaryKey"`
	TemplateID uuid.UUID    `json:"template_id" gorm:"type:char(36);not null;index"`
	Name       string       `json:"name" gorm:"type:varchar(200);not null"`
	CreatedAt  time.Time    `json:"created_at"`
	UpdatedAt  time.Time    `json:"updated_at"`
	CreatedBy  string       `json:"created_by" gorm:"type:varchar(36)"`
	Status     EntityStatus `json:"status" gorm:"type:varchar(20);default:'active'"`

	// 外键关联
	Template *EntityTemplate `json:"template,omitempty" gorm:"foreignKey:TemplateID"`

	// 动态属性值（不存储在数据库中）
	Attributes map[string]interface{} `json:"attributes,omitempty" gorm:"-"`
}

// BeforeCreate GORM钩子：创建前生成UUID
func (e *Entity) BeforeCreate(tx *gorm.DB) error {
	if e.ID == uuid.Nil {
		e.ID = uuid.New()
	}
	return nil
}

// GetAttribute 获取属性值
func (e *Entity) GetAttribute(name string) interface{} {
	if e.Attributes == nil {
		return nil
	}
	return e.Attributes[name]
}

// SetAttribute 设置属性值
func (e *Entity) SetAttribute(name string, value interface{}) {
	if e.Attributes == nil {
		e.Attributes = make(map[string]interface{})
	}
	e.Attributes[name] = value
}

// ToMap 转换为Map格式
func (e *Entity) ToMap() map[string]interface{} {
	result := map[string]interface{}{
		"id":          e.ID,
		"template_id": e.TemplateID,
		"name":        e.Name,
		"created_at":  e.CreatedAt,
		"updated_at":  e.UpdatedAt,
		"created_by":  e.CreatedBy,
		"status":      e.Status,
	}

	// 合并属性值
	if e.Attributes != nil {
		for k, v := range e.Attributes {
			result[k] = v
		}
	}

	return result
}

// AttributeValueString 字符串类型属性值
type AttributeValueString struct {
	ID            uuid.UUID `json:"id" gorm:"type:char(36);primaryKey"`
	EntityID      uuid.UUID `json:"entity_id" gorm:"type:char(36);not null;index:idx_entity_attr_string"`
	AttributeName string    `json:"attribute_name" gorm:"type:varchar(100);not null;index:idx_entity_attr_string"`
	Value         string    `json:"value" gorm:"type:text"`
	CreatedAt     time.Time `json:"created_at"`
	UpdatedAt     time.Time `json:"updated_at"`
}

// BeforeCreate GORM钩子
func (avs *AttributeValueString) BeforeCreate(tx *gorm.DB) error {
	if avs.ID == uuid.Nil {
		avs.ID = uuid.New()
	}
	return nil
}

// AttributeValueNumber 数值类型属性值
type AttributeValueNumber struct {
	ID            uuid.UUID `json:"id" gorm:"type:char(36);primaryKey"`
	EntityID      uuid.UUID `json:"entity_id" gorm:"type:char(36);not null;index:idx_entity_attr_number"`
	AttributeName string    `json:"attribute_name" gorm:"type:varchar(100);not null;index:idx_entity_attr_number"`
	Value         float64   `json:"value" gorm:"type:decimal(20,6)"`
	CreatedAt     time.Time `json:"created_at"`
	UpdatedAt     time.Time `json:"updated_at"`
}

// BeforeCreate GORM钩子
func (avn *AttributeValueNumber) BeforeCreate(tx *gorm.DB) error {
	if avn.ID == uuid.Nil {
		avn.ID = uuid.New()
	}
	return nil
}

// AttributeValueBoolean 布尔类型属性值
type AttributeValueBoolean struct {
	ID            uuid.UUID `json:"id" gorm:"type:char(36);primaryKey"`
	EntityID      uuid.UUID `json:"entity_id" gorm:"type:char(36);not null;index:idx_entity_attr_boolean"`
	AttributeName string    `json:"attribute_name" gorm:"type:varchar(100);not null;index:idx_entity_attr_boolean"`
	Value         bool      `json:"value"`
	CreatedAt     time.Time `json:"created_at"`
	UpdatedAt     time.Time `json:"updated_at"`
}

// BeforeCreate GORM钩子
func (avb *AttributeValueBoolean) BeforeCreate(tx *gorm.DB) error {
	if avb.ID == uuid.Nil {
		avb.ID = uuid.New()
	}
	return nil
}

// AttributeValueDatetime 时间类型属性值
type AttributeValueDatetime struct {
	ID            uuid.UUID `json:"id" gorm:"type:char(36);primaryKey"`
	EntityID      uuid.UUID `json:"entity_id" gorm:"type:char(36);not null;index:idx_entity_attr_datetime"`
	AttributeName string    `json:"attribute_name" gorm:"type:varchar(100);not null;index:idx_entity_attr_datetime"`
	Value         time.Time `json:"value"`
	CreatedAt     time.Time `json:"created_at"`
	UpdatedAt     time.Time `json:"updated_at"`
}

// BeforeCreate GORM钩子
func (avd *AttributeValueDatetime) BeforeCreate(tx *gorm.DB) error {
	if avd.ID == uuid.Nil {
		avd.ID = uuid.New()
	}
	return nil
}

// AttributeValueReference 引用类型属性值
type AttributeValueReference struct {
	ID               uuid.UUID  `json:"id" gorm:"type:char(36);primaryKey"`
	EntityID         uuid.UUID  `json:"entity_id" gorm:"type:char(36);not null;index:idx_entity_attr_reference"`
	AttributeName    string     `json:"attribute_name" gorm:"type:varchar(100);not null;index:idx_entity_attr_reference"`
	Value            uuid.UUID  `json:"value" gorm:"type:char(36);index"`
	TargetTemplateID *uuid.UUID `json:"target_template_id,omitempty" gorm:"type:char(36)"`
	CreatedAt        time.Time  `json:"created_at"`
	UpdatedAt        time.Time  `json:"updated_at"`
}

// BeforeCreate GORM钩子
func (avr *AttributeValueReference) BeforeCreate(tx *gorm.DB) error {
	if avr.ID == uuid.Nil {
		avr.ID = uuid.New()
	}
	return nil
}

// AttributeValueArray 数组类型属性值
type AttributeValueArray struct {
	ID            uuid.UUID       `json:"id" gorm:"type:char(36);primaryKey"`
	EntityID      uuid.UUID       `json:"entity_id" gorm:"type:char(36);not null;index:idx_entity_attr_array"`
	AttributeName string          `json:"attribute_name" gorm:"type:varchar(100);not null;index:idx_entity_attr_array"`
	Value         json.RawMessage `json:"value" gorm:"type:json"`
	CreatedAt     time.Time       `json:"created_at"`
	UpdatedAt     time.Time       `json:"updated_at"`
}

// BeforeCreate GORM钩子
func (ava *AttributeValueArray) BeforeCreate(tx *gorm.DB) error {
	if ava.ID == uuid.Nil {
		ava.ID = uuid.New()
	}
	return nil
}

// AttributeValueJSON JSON类型属性值
type AttributeValueJSON struct {
	ID            uuid.UUID       `json:"id" gorm:"type:char(36);primaryKey"`
	EntityID      uuid.UUID       `json:"entity_id" gorm:"type:char(36);not null;index:idx_entity_attr_json"`
	AttributeName string          `json:"attribute_name" gorm:"type:varchar(100);not null;index:idx_entity_attr_json"`
	Value         json.RawMessage `json:"value" gorm:"type:json"`
	CreatedAt     time.Time       `json:"created_at"`
	UpdatedAt     time.Time       `json:"updated_at"`
}

// BeforeCreate GORM钩子
func (avj *AttributeValueJSON) BeforeCreate(tx *gorm.DB) error {
	if avj.ID == uuid.Nil {
		avj.ID = uuid.New()
	}
	return nil
}

// ValidationRule 验证规则
type ValidationRule struct {
	Type    string      `json:"type"`    // required, min, max, regex, enum, length
	Value   interface{} `json:"value"`   // 验证参数
	Message string      `json:"message"` // 错误消息
}
